package com.codeworker.app.data.entity;

import android.os.Build;

import androidx.annotation.NonNull;
import androidx.annotation.RequiresApi;
import androidx.room.Entity;
import androidx.room.PrimaryKey;

import com.codeworker.app.data.common.enums.BillTypeEnum;
import com.codeworker.app.data.common.enums.PayTypeEnum;
import com.codeworker.app.utils.FormatUtil;

import java.io.Serializable;
import java.time.LocalDateTime;
import java.util.Objects;

/**
 * 账单表
 */
@Entity(tableName = "bill_table")
public class Bill implements Serializable {
    /**
     * 主键
     */
    @PrimaryKey(autoGenerate = true)
    private Integer id;

    /**
     * 收支类型，1为收入，0为支出
     */
    private Integer payType;

    /**
     * 归属账户id，Property表主键
     */
    private Integer propertyId;

    /**
     * 收支金额，以分为单位
     */
    private Integer value;

    /**
     * 记账类型，相关类型具体查看枚举类BillTypeEnum
     */
    private Integer type;

    /**
     * 记账备注
     */
    private String remark;

    /**
     * 记账创建时间
     */
    private String createTime;

    /**
     * 记账更新时间
     */
    private String updateTime;

    /**
     * 记账年份
     */
    private Integer year;

    /**
     * 记账月份
     */
    private Integer month;

    /**
     * 记账日期
     */
    private Integer day;


    @RequiresApi(api = Build.VERSION_CODES.O)
    public Bill(@NonNull Integer payType, @NonNull Integer propertyId, @NonNull Integer value, @NonNull Integer type, String remark) {
        this.payType = payType;
        this.type = type;
        this.value = value;
        this.propertyId = propertyId;
        this.remark = remark;

        //默认值
        LocalDateTime dateTime = LocalDateTime.now();
        this.createTime = FormatUtil.format(dateTime);
        this.year = dateTime.getYear();
        this.month = dateTime.getMonthValue();
        this.day = dateTime.getDayOfMonth();
    }

    @NonNull
    @Override
    public String toString() {
        return "Bill{" +
                "id=" + id +
                ", payType=" + PayTypeEnum.getPayTypeDesc(payType) +
                ", propertyId=" + propertyId +
                ", value=" + value.doubleValue() /100 +
                ", type=" + BillTypeEnum.getBillDesc(payType, type) +
                ", remark='" + remark + '\'' +
                ", createTime=" + createTime +
                ", updateTime=" + updateTime +
                ", year=" + year +
                ", month=" + month +
                ", day=" + day +
                '}';
    }

    @Override
    public boolean equals(Object o) {
        if (this == o) return true;
        if (o == null || getClass() != o.getClass()) return false;

        Bill bill = (Bill) o;

        if (!id.equals(bill.id)) return false;
        if (!payType.equals(bill.payType)) return false;
        if (!propertyId.equals(bill.propertyId)) return false;
        if (!value.equals(bill.value)) return false;
        if (!type.equals(bill.type)) return false;
        if (!Objects.equals(remark, bill.remark)) return false;
        if (!createTime.equals(bill.createTime)) return false;
        if (!year.equals(bill.year)) return false;
        if (!month.equals(bill.month)) return false;
        return day.equals(bill.day);
    }

    @Override
    public int hashCode() {
        int result = id.hashCode();
        result = 31 * result + payType.hashCode();
        result = 31 * result + propertyId.hashCode();
        result = 31 * result + value.hashCode();
        result = 31 * result + type.hashCode();
        result = 31 * result + (remark != null ? remark.hashCode() : 0);
        result = 31 * result + createTime.hashCode();
        result = 31 * result + updateTime.hashCode();
        result = 31 * result + year.hashCode();
        result = 31 * result + month.hashCode();
        result = 31 * result + day.hashCode();
        return result;
    }

    public static Bill clone(Bill oldBill) {
        Bill newBill = new Bill(oldBill.payType, oldBill.propertyId, oldBill.value, oldBill.type, oldBill.remark);
        newBill.id = oldBill.id;
        newBill.createTime = oldBill.createTime;
        newBill.updateTime = oldBill.updateTime;
        newBill.year = oldBill.year;
        newBill.month = oldBill.month;
        newBill.day = oldBill.day;
        return newBill;
    }

    public Integer getId() {
        return id;
    }

    public void setId(Integer id) {
        this.id = id;
    }

    public Integer getPayType() {
        return payType;
    }

    public void setPayType(Integer payType) {
        this.payType = payType;
    }

    public Integer getPropertyId() {
        return propertyId;
    }

    public void setPropertyId(Integer propertyId) {
        this.propertyId = propertyId;
    }

    public Integer getValue() {
        return value;
    }

    public void setValue(Integer value) {
        this.value = value;
    }

    public Integer getType() {
        return type;
    }

    public void setType(Integer type) {
        this.type = type;
    }

    public String getRemark() {
        return remark;
    }

    public void setRemark(String remark) {
        this.remark = remark;
    }

    public String getCreateTime() {
        return createTime;
    }

    public void setCreateTime(String time) {
        this.createTime = time;
    }

    public String getUpdateTime() {
        return updateTime;
    }

    public void setUpdateTime(String time) {
        this.updateTime = time;
    }

    public Integer getYear() {
        return year;
    }

    public void setYear(Integer year) {
        this.year = year;
    }

    public Integer getMonth() {
        return month;
    }

    public void setMonth(Integer month) {
        this.month = month;
    }

    public Integer getDay() {
        return day;
    }

    public void setDay(Integer day) {
        this.day = day;
    }
}
